package com.ray.config;

import at.pollux.thymeleaf.shiro.dialect.ShiroDialect;
import com.ray.realm.AccountRealm;
import org.apache.shiro.authc.credential.HashedCredentialsMatcher;
import org.apache.shiro.mgt.SecurityManager;
import org.apache.shiro.spring.security.interceptor.AuthorizationAttributeSourceAdvisor;
import org.apache.shiro.spring.web.ShiroFilterFactoryBean;
import org.apache.shiro.web.mgt.DefaultWebSecurityManager;
import org.springframework.aop.framework.autoproxy.DefaultAdvisorAutoProxyCreator;
import org.springframework.beans.factory.annotation.Qualifier;
import org.springframework.context.annotation.Bean;
import org.springframework.context.annotation.Configuration;

import java.util.HashMap;
import java.util.Map;

@Configuration
public class ShiroConfig {


    /**
     * 过滤器工厂
     * @Qualifier("securityManager") 将securityManager从spring中取出
     * @Bean（“shiroFilterFactoryBean”）可加可不加
     */
    @Bean
    public ShiroFilterFactoryBean shiroFilterFactoryBean(@Qualifier("securityManager") DefaultWebSecurityManager securityManager){
        ShiroFilterFactoryBean factoryBean = new ShiroFilterFactoryBean();
        factoryBean.setSecurityManager(securityManager);
        //权限设置
        /*
         * anon 无需认证就可访问
         * authc 必须认证才能访问
         * user 必须拥有记住我 才能用
         * perms 必须有权限才能访问
         * role 必须有角色才能访问
         */
        Map<String,String> map = new HashMap<>();
        map.put("/main", "authc");// authc 必须登录
        map.put("/manage", "perms[manage]");// perms 必须有manage权限
        map.put("/admin", "roles[admin]");// roles 必须有admin角色
        factoryBean.setFilterChainDefinitionMap(map);
        //设置登录页面
        factoryBean.setLoginUrl("/login");
        //设置未授权页面
        factoryBean.setUnauthorizedUrl("/unauth");
        return factoryBean;
    }


    /**
     * 安全管理器
     * @Qualifier("accountRealm") 将AccountRealm从spring中取出
     *
     */
    @Bean
    public DefaultWebSecurityManager securityManager(@Qualifier("accountRealm") AccountRealm accountRealm){
        DefaultWebSecurityManager securityManager = new DefaultWebSecurityManager();
        securityManager.setRealm(accountRealm);
        return securityManager;
    }

    /**
     * @Bean 将AccountRealm放入spring容器
     */
//    @Bean
//    public AccountRealm accountRealm(){
//        return new AccountRealm();
//    }
    /**
     * 加入密码匹配
     * 设置2次
     */
    @Bean
    public AccountRealm accountRealm(@Qualifier("passwordMatcher") HashedCredentialsMatcher passwordMatcher){
        AccountRealm userRealm = new AccountRealm();
        userRealm.setCredentialsMatcher(passwordMatcher);
        return new AccountRealm();
    }


    //整合shior-thymeleaf
    @Bean
    public ShiroDialect getShiroDialect(){
        return new ShiroDialect();
    }


    /**
     * 加了后
     */
//    @Bean
//    public DefaultAdvisorAutoProxyCreator defaultAdvisorAutoProxyCreator() {
//        DefaultAdvisorAutoProxyCreator proxyCreator = new DefaultAdvisorAutoProxyCreator();
//        proxyCreator.setProxyTargetClass(true);
//        return proxyCreator;
//    }

    /**
     * 加了后方法上可以使用  @RequiresPermissions("user:add")
     */
    @Bean
    public AuthorizationAttributeSourceAdvisor authorizationAttributeSourceAdvisor(SecurityManager securityManager) {
        AuthorizationAttributeSourceAdvisor advisor = new AuthorizationAttributeSourceAdvisor();
        advisor.setSecurityManager(securityManager);
        return advisor;
    }

    //用来跟加密的密码进行比对的bean

    @Bean(name = "passwordMatcher")
    public HashedCredentialsMatcher getHashedCredentialsMatcher() {
        HashedCredentialsMatcher hashedCredentialsMatcher = new HashedCredentialsMatcher();
        //设置比较规则
        hashedCredentialsMatcher.setHashAlgorithmName("MD5");
        //迭代2次
        hashedCredentialsMatcher.setHashIterations(2);
        return hashedCredentialsMatcher;
    }


}
